﻿//(P∧Q) V (┓P∧R)
//主合取范式: (┓PVQV┓R) ∧ (┓PVQVR) ∧ (PV┓QVR) ∧ (PVQVR)
//主析取范式: (P∧Q∧R) V (P∧Q∧┓R) V (┓P∧Q∧R) V (┓P∧┓Q∧R)
#include <iostream>
#include <cmath>
using namespace std;
int a[1000], b[1000], c[1000];  //P∧Q  ┓P∧R  A
int x[1000], y[1000], z[1000];  //P Q R
int n;


//输出真值表
void Output_truth_table() {
	cout << endl << "真值表:" << endl;
	cout << 'P' << '\t' << 'Q' << '\t' << 'R' << '\t';
	cout << "P∧Q" << '\t' << "┓P∧R" << '\t' << "(P∧Q) V (┓P∧R)" << endl;
	for (int i = 0; i < pow(2, n); ++i) {
		//输出 P Q R 的真值
		if (i < pow(2, n - 1)) {
			x[i] = 1;
			cout << 'T' << '\t';
		}
		if (i >= pow(2, n - 1)) {
			x[i] = 0;
			cout << 'F' << '\t';
		}
		if (i % 4 < 2) {
			y[i] = 1;
			cout << 'T' << '\t';
		}
		if (i % 4 >= 2) {
			y[i] = 0;
			cout << 'F' << '\t';
		}
		if (i % 2 == 0) {
			z[i] = 1;
			cout << 'T' << '\t';
		}
		if (i % 2 == 1) {
			z[i] = 0;
			cout << 'F' << '\t';
		}
		//输出(P∧Q)  (┓P∧R)  (P∧Q) V (┓P∧R) 的真值
		if (a[i] == 1) cout << 'T' << '\t';
		else if (a[i] == 0) cout << 'F' << '\t';
		if (b[i] == 1) cout << 'T' << '\t';
		else if (b[i] == 0) cout << 'F' << '\t';
		if (c[i] == 1) cout << 'T' << endl;
		else if (c[i] == 0) cout << 'F' << endl;
	}
}


//主合取范式
void Master_conjunction() {
	cout << endl << "主合取范式: ";
	int count = 0;
	for (int i = 0; i < pow(2, n); ++i) {
		if (c[i] == 0) {  //如果公式真值为假，则输出相应的真值相反的 P Q R
			if (x[i] == 1 && y[i] == 1 && z[i] == 1) {
				cout << "(┓PV┓QV┓R)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 1 && z[i] == 0) {
				cout << "(┓PV┓QVR)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 0 && z[i] == 1) {
				cout << "(┓PVQV┓R)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 0 && z[i] == 0) {
				cout << "(┓PVQVR)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 1 && z[i] == 1) {
				cout << "(PV┓QV┓R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 1 && z[i] == 0) {
				cout << "(PV┓QVR)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 0 && z[i] == 1) {
				cout << "(PVQV┓R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 0 && z[i] == 0) {
				cout << "(PVQVR)";
				count++;
			}
			if (count != pow(2, n - 1)) cout << " ∧ ";
		}
	}
	cout << endl;
}


//主析取范式
void Master_disjunction() {
	cout << endl << "主析取范式: ";
	int count = 0;
	for (int i = 0; i < pow(2, n); ++i) {
		if (c[i] == 1) {  //如果公式真值为真，则输出相应真值的 P Q R
			if (x[i] == 1 && y[i] == 1 && z[i] == 1) {
				cout << "(P∧Q∧R)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 1 && z[i] == 0) {
				cout << "(P∧Q∧┓R)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 0 && z[i] == 1) {
				cout << "(P∧┓Q∧R)";
				count++;
			}
			else if (x[i] == 1 && y[i] == 0 && z[i] == 0) {
				cout << "(P∧┓Q∧┓R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 1 && z[i] == 1) {
				cout << "(┓P∧Q∧R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 1 && z[i] == 0) {
				cout << "(┓P∧Q∧┓R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 0 && z[i] == 1) {
				cout << "(┓P∧┓Q∧R)";
				count++;
			}
			else if (x[i] == 0 && y[i] == 0 && z[i] == 0) {
				cout << "(┓P∧┓Q∧┓R)";
				count++;
			}
			if (count != pow(2, n - 1)) cout << " V ";
		}
	}
	cout << endl;
}


int main() {
	cout << "请输入变量:";
	cin >> n;
	cout << endl << "公式为:(P∧Q) V (┓P∧R)" << endl;
	int m1 = 0;
	int m2 = 0;
	int m3 = 0;
	//三重循环
	for (int i = 0; i < 2; ++i) {
		for (int j = 0; j < 2; ++j) {
			for (int k = 0; k < 2; ++k) {
				if (i == 0 && j == 0) {
					a[m1++] = 1;  //P为真，Q为真：P∧Q 为真
				}
				if (j == 1 || i == 1) {
					a[m1++] = 0;  //P为真，Q为假 或 P为假：P∧Q 为假
				}
				if (i == 0 || k == 1) {
					b[m2++] = 0;  //P为真 或 P为假，R为假：(┓P∧R)为假
				}
				if (i == 1 && k == 0) {
					b[m2++] = 1;  //P为假 且 R为真：(┓P∧R)为真
				}
			}
		}
	}
	for (int m3 = 0; m3 < pow(2, n); ++m3) {
		if (a[m3] == 0 && b[m3] == 0) {  //P∧Q 为假 且 (┓P∧R)为假
			c[m3] = 0;
		}
		else c[m3] = 1;
	}
	Output_truth_table();
	Master_conjunction();
	Master_disjunction();
	return 0;
}